package com.hbl.cgs.cgsagent.plugin;

import com.fasterxml.jackson.databind.JsonNode;
import com.hbl.cgs.cgsagent.Constants;
import com.hbl.cgs.cgsagent.Utils;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;

import java.util.Map;

public class DefaultInputPluginFactory implements InputPluginFactory{
    @Override
    public InputPlugin create(JsonNode context) throws PluginConfigException {
        String name = context.get(Constants.KEY_PLUGIN_NAME).asText();
        JsonNode pluginContext = context.get(Constants.KEY_PLUGIN_CONTEXT);
        Map<String, String> contextMap = Utils.jsonNode2Map(pluginContext);

        String classType = context.get(Constants.KEY_PLUGIN_TYPE).asText();
        Class<? extends InputPlugin> inputPluginClass = getPluginClass(classType);
        try {
            InputPlugin inputPlugin = SpringContextUtils.getBean(inputPluginClass);
            inputPlugin.setName(name);
            inputPlugin.configure(contextMap);
            return inputPlugin;
        } catch (BeansException e) {
            e.printStackTrace();
            throw new PluginConfigException("unable to load plugin");
        }
    }

    private Class<? extends InputPlugin> getPluginClass(String classType) throws PluginConfigException{
        InputPluginType inputPluginType = InputPluginType.OTHER;
        try {
            inputPluginType = InputPluginType.valueOf(classType.toUpperCase());
        } catch (IllegalArgumentException e) {
            e.printStackTrace();
        }
        String inputPluginClassName = inputPluginType.equals(InputPluginType.OTHER) ? classType : inputPluginType.getClassName();
        try {
            return (Class<? extends InputPlugin>) Class.forName(inputPluginClassName);
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
            throw new PluginConfigException("unable to load input plugin type");
        }
    }

    @Override
    public Class<? extends InputPlugin> getClass(String type) throws PluginConfigException {
        return null;
    }
}
